/*
 * receiver.wsdl web service operations
 * implemention
 *
 */

#include "../soapH.h"
#include "../onvif.h"
#include "receiver_service.h"

int init_receiverservice_configs(void)
{
	memset(receiver_configurations,0,sizeof(receiver_configurations));

	query_all_config_default(CLASS_RVRCONF,&receiver_configurations[0][0],SUPPORT_RVRS_NUM,&receiver_config_num, RVR_MAX_POS);

	return 0;
}

int exit_receiverservice_configs(void)
{
	free_all_space(&receiver_configurations[0][0],SUPPORT_RVRS_NUM,RVR_MAX_POS);
	memset(receiver_configurations,0,sizeof(receiver_configurations));

	return 0;
}

int transform_rvrstruct_array(struct tt__Receiver *receiver, char *array[], int size)
{
	char buff[512]={0};

	if(receiver == NULL || array == NULL || size > RVR_MAX_POS)
		return -1;

	cmp_and_cpy(array+RVR_TOKEN,receiver->Token);
	
	snprintf(buff,512,"%d",receiver->Configuration->Mode);
	cmp_and_cpy(array+RVR_MODE,buff);

	cmp_and_cpy(array+RVR_MEDIAURI,receiver->Configuration->MediaUri);
	
	snprintf(buff,512,"%d;%d;",receiver->Configuration->StreamSetup->Stream,
			receiver->Configuration->StreamSetup->Transport->Protocol);
	cmp_and_cpy(array+RVR_STREAMSETUP,buff);

	snprintf(buff, 512, "%d", receiver->__size);
	cmp_and_cpy(array+RVR_ANYSIZE,buff);
	cmp_and_cpy(array+RVR_ANY,receiver->__any);
	cmp_and_cpy(array+RVR_ANYARRT,receiver->__anyAttribute);

	return 0;
}

int get_receiverservice_cap(struct soap *soap, struct trv__Capabilities * receiver)
{
	if(soap == NULL || receiver == NULL)
	{
		DBG("invalid params!\n");
		return -1;
	}

	receiver->__size = 0;
	receiver->__any = NULL;
	receiver->__anyAttribute = NULL;

	receiver->MaximumRTSPURILength = (int*)soap_malloc(soap, sizeof(int));
	receiver->RTP_USCOREMulticast = (enum xsd__boolean*)soap_malloc(soap, sizeof(enum xsd__boolean));
	receiver->RTP_USCORERTSP_USCORETCP = (enum xsd__boolean*)soap_malloc(soap, sizeof(enum xsd__boolean));
	receiver->RTP_USCORETCP = (enum xsd__boolean*)soap_malloc(soap, sizeof(enum xsd__boolean));
	
	*receiver->MaximumRTSPURILength = XADDR_LEN;
	*receiver->RTP_USCOREMulticast = media_caps[RTP_MULTICAST];
	*receiver->RTP_USCORERTSP_USCORETCP = media_caps[RTP_RTSP_TCP];
	*receiver->RTP_USCORETCP = media_caps[RTP_TCP];
	receiver->SupportedReceivers = 4;

	return 0;
}

static int get_receiver_config(struct soap *soap, int pos, struct tt__Receiver *rvr_config)
{
	if(pos < 0 || pos > RVR_MAX_POS || rvr_config == NULL)
		return -1;

	char **cfg = receiver_configurations[pos];	

	rvr_config->Token = (char *)soap_malloc(soap,sizeof(char)*TOKEN_LEN);
	strncpy(rvr_config->Token, cfg[RVR_TOKEN], TOKEN_LEN);

	rvr_config->Configuration = (struct tt__ReceiverConfiguration *)soap_malloc(soap,sizeof(struct tt__ReceiverConfiguration));
	rvr_config->Configuration->Mode = atoi(cfg[RVR_MODE]);
	rvr_config->Configuration->MediaUri = (char *)soap_malloc(soap, sizeof(char)*XADDR_LEN);
	strncpy(rvr_config->Configuration->MediaUri,cfg[RVR_MEDIAURI],XADDR_LEN);
	
	rvr_config->Configuration->StreamSetup = (struct tt__StreamSetup *)soap_malloc(soap,sizeof(struct tt__StreamSetup));
	rvr_config->Configuration->StreamSetup->Transport = (struct tt__Transport *)soap_malloc(soap,sizeof(struct tt__Transport));
	sscanf(cfg[RVR_STREAMSETUP],"%d;%d;",&rvr_config->Configuration->StreamSetup->Stream,
			&rvr_config->Configuration->StreamSetup->Transport->Protocol);	
	rvr_config->Configuration->StreamSetup->Transport->Tunnel = NULL;
	rvr_config->Configuration->StreamSetup->__size = 0;
	rvr_config->Configuration->StreamSetup->__any = NULL;
	rvr_config->Configuration->StreamSetup->__anyAttribute = NULL;

	rvr_config->Configuration->__size = 0;
	rvr_config->Configuration->__any = NULL;
	rvr_config->Configuration->__anyAttribute = NULL;

	rvr_config->__size = 0;
	rvr_config->__any = NULL;
	rvr_config->__anyAttribute = NULL;

	return 0;
}

static int search_rvrtoken_pos(const char *token)
{
	int pos = 0;

	pos = search_matchtoken_pos(&receiver_configurations[0][0],SUPPORT_RVRS_NUM,RVR_MAX_POS,token,RVR_TOKEN);

	return pos;
}

//=========================================================================//
/** Auto-test server operation __trv__GetServiceCapabilities */
int __trv__GetServiceCapabilities(struct soap *soap, struct _trv__GetServiceCapabilities *trv__GetServiceCapabilities, struct _trv__GetServiceCapabilitiesResponse *trv__GetServiceCapabilitiesResponse)
{	
	/* Return incomplete response with default data values */
	INFO(stderr);

	trv__GetServiceCapabilitiesResponse->Capabilities = (struct trv__Capabilities *)soap_malloc(soap, sizeof(struct trv__Capabilities));
	get_receiverservice_cap(soap, trv__GetServiceCapabilitiesResponse->Capabilities);

	return SOAP_OK;
}


/** Auto-test server operation __trv__GetReceivers */
int __trv__GetReceivers(struct soap *soap, struct _trv__GetReceivers *trv__GetReceivers, struct _trv__GetReceiversResponse *trv__GetReceiversResponse)
{	
	/* Return incomplete response with default data values */
	INFO(stderr);

	int size = receiver_config_num;
	int i;

	trv__GetReceiversResponse->__sizeReceivers = size;
	trv__GetReceiversResponse->Receivers = (struct tt__Receiver *)soap_malloc(soap,sizeof(struct tt__Receiver)*size);

	for(i = 0;i < size;i++)
	{
		get_receiver_config(soap,i,trv__GetReceiversResponse->Receivers+i);
	}

	return SOAP_OK;
}


/** Auto-test server operation __trv__GetReceiver */
int __trv__GetReceiver(struct soap *soap, struct _trv__GetReceiver *trv__GetReceiver, struct _trv__GetReceiverResponse *trv__GetReceiverResponse)
{	
	/* Return incomplete response with default data values */
	INFO(stderr);

	int id = 0;
	trv__GetReceiverResponse->Receiver = (struct tt__Receiver *)soap_malloc(soap,sizeof(struct tt__Receiver));
	id = search_rvrtoken_pos(trv__GetReceiver->ReceiverToken); 
	get_receiver_config(soap,id,trv__GetReceiverResponse->Receiver);

	return SOAP_OK;
}


/** Auto-test server operation __trv__CreateReceiver */
int __trv__CreateReceiver(struct soap *soap, struct _trv__CreateReceiver *trv__CreateReceiver, struct _trv__CreateReceiverResponse *trv__CreateReceiverResponse)
{	
	/* Return incomplete response with default data values */
	INFO(stderr);

	trv__CreateReceiverResponse->Receiver = (struct tt__Receiver *)soap_malloc(soap,sizeof(struct tt__Receiver));
	trv__CreateReceiverResponse->Receiver->Token = (char *)soap_malloc(soap,sizeof(char)*TOKEN_LEN);
	//generate a unique token
	time_t now = time(NULL);
	strftime(trv__CreateReceiverResponse->Receiver->Token,TOKEN_LEN,"receiver-%y%m%d-%H%M%S",localtime(&now));
	trv__CreateReceiverResponse->Receiver->Configuration = trv__CreateReceiver->Configuration;
	trv__CreateReceiverResponse->Receiver->__size = 0;
	trv__CreateReceiverResponse->Receiver->__any = NULL;
	trv__CreateReceiverResponse->Receiver->__anyAttribute = NULL;
	if(receiver_config_num < SUPPORT_RVRS_NUM)
	{
		transform_rvrstruct_array(trv__CreateReceiverResponse->Receiver,receiver_configurations[receiver_config_num++], RVR_MAX_POS);
		insert_config_default_byarray(CLASS_RVRCONF,trv__CreateReceiverResponse->Receiver->Token, receiver_configurations[receiver_config_num-1],RVR_MAX_POS);
	}
	else
	{
		DBG("can't create receivers as exceeding the supported receivers number.\n");
	}

	return SOAP_OK;
}


/** Auto-test server operation __trv__DeleteReceiver */
int __trv__DeleteReceiver(struct soap *soap, struct _trv__DeleteReceiver *trv__DeleteReceiver, struct _trv__DeleteReceiverResponse *trv__DeleteReceiverResponse)
{	
	INFO(stderr);

	int pos = 0;
	pos = search_rvrtoken_pos(trv__DeleteReceiver->ReceiverToken); 
	if(pos >= 0)
	{
		free_all_space(&receiver_configurations[0][0],SUPPORT_RVRS_NUM,RVR_MAX_POS);
		receiver_config_num -= 1;
		delete_config_default(CLASS_RVRCONF,trv__DeleteReceiver->ReceiverToken);
		query_all_config_default(CLASS_RVRCONF,&receiver_configurations[0][0],SUPPORT_RVRS_NUM,&receiver_config_num,RVR_MAX_POS);
	}

	return SOAP_OK;
}


/** Auto-test server operation __trv__ConfigureReceiver */
int __trv__ConfigureReceiver(struct soap *soap, struct _trv__ConfigureReceiver *trv__ConfigureReceiver, struct _trv__ConfigureReceiverResponse *trv__ConfigureReceiverResponse)
{	
	INFO(stderr);

	int pos = 0;
	pos = search_rvrtoken_pos(trv__ConfigureReceiver->ReceiverToken);
	struct tt__Receiver rvr;
	rvr.Token = trv__ConfigureReceiver->ReceiverToken;
	rvr.Configuration = trv__ConfigureReceiver->Configuration;
	rvr.__size = 0;
	rvr.__any = NULL;
	rvr.__anyAttribute = NULL;
	if(pos >= 0)
	{
		transform_rvrstruct_array(&rvr, receiver_configurations[pos], RVR_MAX_POS);
		update_config_default_byarray(CLASS_RVRCONF,rvr.Token,receiver_configurations[pos], RVR_MAX_POS);
	}

	return SOAP_OK;
}


/** Auto-test server operation __trv__SetReceiverMode */
int __trv__SetReceiverMode(struct soap *soap, struct _trv__SetReceiverMode *trv__SetReceiverMode, struct _trv__SetReceiverModeResponse *trv__SetReceiverModeResponse)
{	
	INFO(stderr);

	int pos = 0;
	char tmp[16]={0};
	pos = search_rvrtoken_pos(trv__SetReceiverMode->ReceiverToken);
	snprintf(tmp,16,"%d",trv__SetReceiverMode->Mode);
	if(pos >= 0)
	{
		cmp_and_cpy(receiver_configurations[pos]+RVR_MODE, tmp);
		update_config_default_byarray(CLASS_RVRCONF,trv__SetReceiverMode->ReceiverToken,receiver_configurations[pos], RVR_MAX_POS);
	}

	return SOAP_OK;
}


/** Auto-test server operation __trv__GetReceiverState */
int __trv__GetReceiverState(struct soap *soap, struct _trv__GetReceiverState *trv__GetReceiverState, struct _trv__GetReceiverStateResponse *trv__GetReceiverStateResponse)
{	
	/* Return incomplete response with default data values */
	INFO(stderr);

	int pos = 0;
	pos = search_rvrtoken_pos(trv__GetReceiverState->ReceiverToken);
	if(pos >= 0)
	{
		trv__GetReceiverStateResponse->ReceiverState = (struct tt__ReceiverStateInformation*)soap_malloc(soap,sizeof(struct tt__ReceiverStateInformation));
		trv__GetReceiverStateResponse->ReceiverState->State = receiver_stat_info[pos][0];
		trv__GetReceiverStateResponse->ReceiverState->AutoCreated = receiver_stat_info[pos][1];
		trv__GetReceiverStateResponse->ReceiverState->__size = 0;
		trv__GetReceiverStateResponse->ReceiverState->__any = NULL;
		trv__GetReceiverStateResponse->ReceiverState->__anyAttribute = NULL;
	}

	return SOAP_OK;
}
